<?php

declare(strict_types=1);

namespace App\Controller\Home\Drp;

use AdaPaySdk\Payment;
use App\Constants\ErrorCode;
use App\Model\Admin\Admin;
use App\Model\BalanceOrder;
use App\Model\ChargeDetail;
use App\Model\ChargeOption;
use App\Model\Device;
use App\Model\Order;
use App\Model\Station;
use App\Services\DeviceService;
use App\Services\Iot\IotService1;
use App\Services\Iot\IotService1 as IotService;
use Hyperf\DbConnection\Db;
use Hyperf\Redis\Redis;
use Hyperf\HttpServer\Contract\RequestInterface;
use Psr\Container\ContainerExceptionInterface;
use Psr\Container\NotFoundExceptionInterface;
use Psr\Http\Message\ResponseInterface;
use Psr\SimpleCache\InvalidArgumentException;
use RedisException;
use Trait\ResponseMsg;
use App\Model\Normal;
use Hyperf\Di\Annotation\Inject;
use Util\Common;
use App\Controller\AbstractController;
use App\Model\Distributors;

class HomeDeviceController extends AbstractController
{
    use ResponseMsg;

    protected Redis $redis;
    protected Normal $normal;

    #[Inject]
    protected Station $station;

    #[Inject]
    protected ChargeOption $chargeOption;

    #[Inject]
    protected Distributors $distributors;

    #[Inject]
    protected Device $device;

    public function __construct()
    {
        $this->redis = container()->get(Redis::class);
        $this->normal = container()->get(Normal::class);
    }

    /**我的设备统计
     * @param RequestInterface $request
     * @return ResponseInterface
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public function statics(RequestInterface $request): ResponseInterface
    {
        $info = $this->distributors->getInfo($request);
        if (!$info) {
            return $this->error(code: '400', msg: '登录态失效 请重新登录');
        }
        $station_id = $request->input('station_id', 0);
        try {
            $baseQuery= $this->device->where('distributor_id', $info['id']);
            if($station_id){
                $baseQuery->where('station_id', $station_id);
            }
            // 获取总设备数
            $data['all'] = $baseQuery->count();
            // 获取在线设备数
            $data['inline'] = (clone $baseQuery)->where('inline', 1)->count();
            // 获取离线设备数
            $data['off'] = (clone $baseQuery)->where('inline', 0)->count();
            return $this->success($data);
        } catch (\Exception $e) {
            Normal::logger($e->getMessage() . $e->getTraceAsString(), 'home');
            return $this->error($e->getMessage());
        }
    }

    /**经销商设备列表
     * @param RequestInterface $request
     * @return ResponseInterface
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public function list(RequestInterface $request): ResponseInterface
    {
        $page = $request->inputs(['page', 'limit', 'keyword', 'inline', 'is_active', 'station_id']);
        $info = $this->distributors->getInfo($request);
        try {
            $query = $this->device->query();
            $query->where(function ($query) use ($page, $info) {
                if (array_key_exists('keyword', $page) && $page['keyword']) {
                    $query->where('sn', 'like', '%' . $page['keyword'] . '%');
                }
                if ($page['inline'] != '') {
                    $query->where('inline', $page['inline']);
                }
                if ($page['is_active'] != '') {
                    $query->where('is_active', $page['is_active']);
                }
                if ($page['station_id']) {
                    $query->where('station_id', $page['station_id']);
                }
                $query->where('distributor_id', $info['id']);
            })->orderBy('station_id', 'desc')
                ->with(['station' => function ($query) {
                    $query->select('id', 'name');
                }])
                ->offset(($page['page'] - 1) * $page['limit'])
                ->limit($page['limit'])
                ->get()->toArray();
            $data['total'] = $query->count();
            $data['list'] = $query->get();
            return $this->success($data);
        } catch (\Exception $e) {
            Normal::logger($e->getMessage() . $e->getTraceAsString(), 'home');
            return $this->error($e->getMessage());
        }
    }

    /**设备管理---编辑
     * @param RequestInterface $request
     * @return ResponseInterface
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public function edit(RequestInterface $request): ResponseInterface
    {
        try {
            $params = $request->inputs(['is_active', 'sn']);
            $info = $this->distributors->getInfo($request);
            if (!$info) {
                return $this->error(code: '400', msg: '登录态失效 请重新登录');
            }
            if (!isset($params['sn'])) {
                return $this->error('1001', '设备编号不能为空');
            }
            $device = $this->device->where('sn', $params['sn'])
                ->where('distributor_id', $info['id'])
                ->first();
            if (!$device) {
                return $this->error('1002', '您的设备下暂无此编号');
            }
            $device->is_active = $params['is_active'];
            $device->save();
            return $this->success();
        } catch (\Exception $e) {
            Normal::logger($e->getMessage() . $e->getTraceAsString(), 'home');
            return $this->error($e->getMessage());
        }
    }


    /**解绑设备
     * @param RequestInterface $request
     * @return ResponseInterface
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public function del(RequestInterface $request): ResponseInterface
    {
        $sn = $request->input('sn', 0, 'int');
        if (!$sn) {
            return $this->error(code: 1001, msg: '登录态失效 请重新登录');
        }
        $device = $this->device->where('sn', $sn)->first();
        if (!$device) {
            return $this->error(code: 1002, msg: '设备不存在');
        }
        $device->station_id = 0;
        $device->save();
        return $this->success();
    }

    /**读取配置
     * @param RequestInterface $request
     * @return ResponseInterface
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public function readParams(RequestInterface $request): ResponseInterface
    {

        $sn = $request->input('sn', 0, 'int');
        if (!$sn) {
            return $this->error('1001', '缺少参数设备编号');
        }
        $device = $this->device->query()->where('sn', $sn)->firstOrFail();
        $data['fd'] = $device->fd;
        $data['sn'] = $device->sn;
        $response = DeviceService::postTcp('/tcp/getParams', $data);
        $responseData = json_decode($response->getBody()->getContents(), true);
        if ($response->getStatusCode() == 200) {
            if ($responseData['code'] == 200) {
                return $this->success(msg: '读取成功 请稍后刷新列表查看');
            } else {
                return $this->error(1001, $responseData['msg']);
            }
        } else {
            return $this->error(msg: '读取失败: ' . ($responseData['message'] ?? '未知错误'));
        }
    }


    public function updateParams(RequestInterface $request): ResponseInterface
    {
        $data = $request->inputs(['sn', 'heart_cycle', 'report_cycle',
            'full_charge_power', 'full_charge_delay', 'null_charge_delay',
            'single_max_power']);

        $device = $this->device->where('sn', $data['sn'])->first();
        $device->fill($data);
        $device->save();
        $data['fd'] = $device->fd;
        $response = DeviceService::postTcp('/tcp/setParams', $data);
        $responseData = json_decode($response->getBody()->getContents(), true);
        if ($response->getStatusCode() == 200) {
            if ($responseData['code'] == 200) {
                return $this->success(msg: '设置成功 请稍后刷新列表查看');
            } else {
                return $this->error(1001, $responseData['msg']);
            }
        } else {
            return $this->error(msg: '设置失败: ' . ($responseData['message'] ?? '未知错误'));
        }
    }

    /**设备详情
     * @param RequestInterface $request
     * @return ResponseInterface
     */
    public function detail(RequestInterface $request): ResponseInterface
    {
        $sn = $request->input('sn');
        $sn = trim($sn);
        if (!$sn) {
            return $this->error(1001, '设备编号不能为空');
        }
        try {
            $device = $this->device->where('sn', $sn)
                ->with('station')
                ->with('station.charge')
                ->withCount('orders')
                ->with('port')
                ->first();
            if (!$device) {
                return $this->error(1001, '设备不存在');
            }
            return $this->success($device);
        } catch (\Exception $e) {
            return $this->error($e->getMessage());
        }
    }

    /**默认设备参数
     * @param RequestInterface $request
     * @return ResponseInterface
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public function normalParams(RequestInterface $request): ResponseInterface
    {
        $info = $this->distributors->getInfo($request);
        if (!$info) {
            return $this->error(code: '400', msg: '登录态失效 请重新登录');
        }
        $deviceId = $request->input('device_id');
        if (!$deviceId) {
            return $this->error('1001', '缺少参数设备id');
        }
        try {
            $device = $this->device->where('id', $deviceId)
                ->first();
            if ($device) {
                return $this->success($device);
            }
            return $this->error('1002', '设备不存在');
        } catch (\Exception $e) {
            return $this->error('1001', $e->getMessage());
        }
    }


    /**我的设备订单
     * @param RequestInterface $request
     * @return ResponseInterface
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public function orderList(RequestInterface $request): ResponseInterface
    {
        $info = $this->distributors->getInfo($request);
        if (!$info) {
            return $this->error(code: '400', msg: '登录态失效 请重新登录');
        }
        $page = $request->inputs(['sn', 'page', 'limit', 'start', 'end', 'status', 'distributor_id','device_id']);
        if (!$page['distributor_id']) {
            $page['distributor_id'] = $info['id'];
        }
        try {
            $query = Order::where(function ($query) use ($page) {
                if (array_key_exists('start', $page) && $page['start']) {
                    $query->where('created_at', '>=', $page['start']);
                }
                if (array_key_exists('end', $page) && $page['end']) {
                    $query->where('created_at', '<=', $page['end']);
                }
                if (array_key_exists('status', $page) && $page['status']) {
                    $query->where('status', $page['status']);
                }
                if (isset($page['sn']) && $page['sn']) {
                    $query->where('sn', $page['sn']);
                } else {
                    $query->where('distributor_id', $page['distributor_id']);
                }
                if(isset($page['device_id']) && $page['device_id']){
                    $query->where('device_id', $page['device_id']);
                }
            })
                ->with([
                    'station' => function ($query) {
                        $query->select('id', 'name'); // 只选择 distributor 的 id 和 phone 字段
                    },
                    'distributor' => function ($query) {
                        $query->select('id', 'customer_service_phone'); // 只选择 distributor 的 id 和 phone 字段
                    },
                    'charge',
                    'charge.time_children',
                    'charge.power_children',
                    'charge.service_children',
                    'detail'
                ]);
            $data['total'] = $query->count();
            $data['list'] = $query->offset(($page['page'] - 1) * $page['limit'])
                ->limit($page['limit'])
                ->orderBy('id', 'desc')->get();


            return $this->success($data);
        } catch (\Exception $e) {
            Normal::logger($e->getMessage() . $e->getTraceAsString(), 'home');
            return $this->error(1001, $e->getMessage());
        }
    }


    /**
     * @param RequestInterface $request
     * @return ResponseInterface
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public function balanceList(RequestInterface $request): ResponseInterface
    {
        try {
            $info = $this->distributors->getInfo($request);
            if (!$info) {
                return $this->error(code: '400', msg: '登录态失效 请重新登录');
            }
            $page = $request->inputs(['page', 'limit', 'status', 'start', 'end']);
            if ($info['level'] == Distributors::LEVEL_1) {
                $devices = Device::where('distributor_id', $info['id'])
                    ->get(['id']);
            } else {
                $devices = Device::where('child_distributor_id', $info['id'])
                    ->get(['id']);
            }
            $inDevices = [];
            $data['list'] = [];
            $data['total'] = 0;
            if ($devices) {
                foreach ($devices as $k => $v) {
                    $inDevices[] = $v['id'];
                }
                $data['list'] = BalanceOrder::whereIn('device_id', $inDevices)
                    ->where(function ($query) use ($page) {
                        if (array_key_exists('start', $page) && $page['start']) {
                            $query->where('created_at', '>=', $page['start']);
                        }
                        if (array_key_exists('end', $page) && $page['end']) {
                            $query->where('created_at', '<=', $page['end']);
                        }
                        if ($page['status']) {
                            $query->where('status', $page['status']);
                        }
                    })
                    ->offset(($page['page'] - 1) * $page['limit'])
                    ->limit($page['limit'])
                    ->get()->toArray();
                foreach ($data['list'] as $k => $v) {
                    $data['list'][$k]['sn'] = $this->device
                        ->where('id', $v['device_id'])
                        ->value('sn');
                }
                $data['total'] = BalanceOrder::whereIn('device_id', $inDevices)
                    ->where(function ($query) use ($page) {
                        if (array_key_exists('start', $page) && $page['start']) {
                            $query->where('created_at', '>=', $page['start']);
                        }
                        if (array_key_exists('end', $page) && $page['end']) {
                            $query->where('created_at', '<=', $page['end']);
                        }
                        if ($page['status']) {
                            $query->where('status', $page['status']);
                        }
                    })
                    ->count();
            }
            return $this->success($data);
        } catch (\Exception $e) {
            Normal::logger($e->getMessage() . $e->getTraceAsString(), 'home');
            return $this->error(1001, $e->getMessage());
        }
    }

    /**开启端口设备
     * @param RequestInterface $request
     * @return ResponseInterface
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public function startPort(RequestInterface $request): ResponseInterface
    {
        $params = $request->post();
        try {
            // 查找设备
            $device = $this->device->where('sn', $params['sn'])->first();
            if (!$device) {
                return $this->error(1001, '设备不存在');
            }

            // 检查设备在线状态
            if (!$device->fd || $device->inline != 1) {
                return $this->error(1001, '设备未在线');
            }

            Db::beginTransaction();

            // 创建订单
            $number = $this->normal->randOrder($device->id);
            $order = new Order();
            $order->device_id = $device->id;
            $order->sn = $device->sn;
            $order->number = $number;
            $order->status = Order::STATUS_PAID;
            $order->payment_type = Order::ADMIN;
            $order->channel_number = $params['channel_number'];
            $order->station_id = $device->station_id;
            $order->fee = 0;
            $order->minutes = $params['minutes'];
            $order->distributor_id = $device->distributor_id;
            $order->power_fee = $params['fee'];
            $order->save();

            // 准备发送数据
            $post = [
                'fd' => $device->fd,
                'sn' => $device->sn,
                'number' => $number,
                'channel_number' => $params['channel_number'],
                'duration' => (int)($params['minutes'] * 60),
                'power_fee' => (int)($params['fee'] * 100)
            ];

            // 发送TCP请求
            $response = DeviceService::postTcp('/tcp/start', $post);
            $responseData = json_decode($response->getBody()->getContents(), true);
            if ($response->getStatusCode() == 200) {
                if ($responseData['code'] == 200) {
                    Db::commit();
                    return $this->success(msg: '开启成功');
                } else {
                    Db::rollBack();
                    return $this->error(1001, $responseData['msg'] ?? '开启失败');
                }
            } else {
                Db::rollBack();
                return $this->error(1001, '开启失败: ' . ($responseData['message'] ?? '未知错误'));
            }

        } catch (\Exception $e) {
            Db::rollBack();
            return $this->error(1001, '操作异常: ' . $e->getMessage());
        }
    }


}
